package com.jzo2o.customer.service.impl;

import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.jzo2o.api.customer.dto.response.AddressBookResDTO;
import com.jzo2o.common.expcetions.DBException;
import com.jzo2o.common.expcetions.ForbiddenOperationException;
import com.jzo2o.common.model.PageResult;
import com.jzo2o.common.utils.BeanUtils;
import com.jzo2o.common.utils.CollUtils;
import com.jzo2o.common.utils.StringUtils;
import com.jzo2o.customer.mapper.AddressBookMapper;
import com.jzo2o.customer.model.domain.AddressBook;
import com.jzo2o.customer.model.dto.request.AddressBookPageQueryReqDTO;
import com.jzo2o.customer.model.dto.request.AddressBookUpsertReqDTO;
import com.jzo2o.customer.service.IAddressBookService;
import com.jzo2o.mvc.utils.UserContext;
import com.jzo2o.mysql.utils.PageHelperUtils;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

/**
 * <p>
 * 地址薄 服务实现类
 * </p>
 *
 * @author itcast
 * @since 2023-07-06
 */
@Service
public class AddressBookServiceImpl extends ServiceImpl<AddressBookMapper, AddressBook> implements IAddressBookService {

    @Override
    public List<AddressBookResDTO> getByUserIdAndCity(Long userId, String city) {

        List<AddressBook> addressBooks = lambdaQuery()
                .eq(AddressBook::getUserId, userId)
                .eq(AddressBook::getCity, city)
                .list();
        if(CollUtils.isEmpty(addressBooks)) {
            return new ArrayList<>();
        }
        return BeanUtils.copyToList(addressBooks, AddressBookResDTO.class);
    }

    /**
     * 新增地址簿
     *
     * @param dto
     */
    @Override
    public void add(AddressBookUpsertReqDTO dto) {
        //1. 参数校验
        if (dto == null) {
            throw new ForbiddenOperationException("参数非法");
        }

        //获取当前登录用户id
        Long userId = UserContext.currentUserId();

        //2. 判断当前新增的地址是否是默认地址,如果是,则删久存新
        if (dto.getIsDefault() == 1){
            AddressBook addressBook = this.lambdaQuery().eq(AddressBook::getIsDefault, 1)
                    .eq(AddressBook::getUserId,userId)
                    .one();
            if (addressBook != null){
                boolean result = this.lambdaUpdate().set(AddressBook::getIsDefault, 0)
                        .eq(AddressBook::getId, addressBook.getId())
                        .update();
                if (!result){
                    throw new DBException("更新默认地址失败");
                }
            }
        }

        //3. 新增地址簿
        AddressBook addressBook = BeanUtil.toBean(dto, AddressBook.class);

        addressBook.setUserId(userId);
        if (StringUtils.isNotEmpty(dto.getLocation())){
            String[] split = dto.getLocation().split(",");
            double lon = Double.parseDouble(split[0]);
            double lat = Double.parseDouble(split[1]);
            addressBook.setLon(lon);
            addressBook.setLat(lat);
        }
        addressBook.setIsDeleted(0);
        boolean result = this.save(addressBook);
        if (!result){
            throw new DBException("新增地址簿失败");
        }
    }

    /**
     * 地址簿分页查询
     *
     * @param dto
     * @return
     */
    @Override
    public PageResult<AddressBookResDTO> pageList(AddressBookPageQueryReqDTO dto) {
        Long userId = UserContext.currentUserId();
        PageResult<AddressBookResDTO> pageResult = PageHelperUtils.selectPage(dto, () -> baseMapper.pageList(userId));
        return pageResult;
    }

    /**
     * 更新地址簿
     *
     * @param dto
     */
    @Override
    public void updateAB(Long id,AddressBookUpsertReqDTO dto) {
        //1. 参数校验
        if (dto == null){
            throw new ForbiddenOperationException("参数非法");
        }

        //获取用户id
        Long userId = UserContext.currentUserId();

        //2. 更新
        AddressBook addressBook = BeanUtil.toBean(dto, AddressBook.class);
        if (addressBook.getIsDefault() == 1){
            AddressBook addressBookDB = this.lambdaQuery().eq(AddressBook::getIsDefault, 1)
                    .eq(AddressBook::getUserId,userId)
                    .one();
            if (addressBookDB != null){
                boolean result = this.lambdaUpdate().set(AddressBook::getIsDefault, 0)
                        .eq(AddressBook::getId, addressBookDB.getId())
                        .update();
                if (!result){
                    throw new DBException("更新默认地址失败");
                }
            }
            addressBook.setIsDefault(1);
        }
        addressBook.setId(id);
        boolean result = this.updateById(addressBook);
        if (!result){
            throw new DBException("更新失败");
        }
    }



    /**
     * 地址簿删除
     *
     * @param ids
     */
    @Override
    public void batchDelete(String ids) {
        System.err.println("ids是: " + ids);
        List<Long> idList = parseIdList(ids);
        idList.forEach(x->{
            boolean result = this.lambdaUpdate().set(AddressBook::getIsDeleted, 1)
                    .eq(AddressBook::getId, x).update();
            if (!result){
                throw new DBException("删除失败");
            }
        });
    }

    private static final ObjectMapper objectMapper = new ObjectMapper();

    /**
     * 将 JSON 格式的字符串列表转换为 List<Long>
     *
     * @param idsJson JSON 字符串，如：["1234567890123456789","9876543210987654321"]
     * @return 转换后的 Long 列表
     */
    private static List<Long> parseIdList(String idsJson) {
        if (idsJson == null || idsJson.trim().isEmpty()) {
            return new ArrayList<>();
        }

        try {
            // 先解析成 String 列表
            List<String> stringList = objectMapper.readValue(idsJson, new TypeReference<List<String>>() {});

            // 转换为 Long 类型并去重
            return stringList.stream()
                    .map(Long::parseLong)
                    .distinct() // 去重
                    .collect(Collectors.toList());
        } catch (Exception e) {
            throw new RuntimeException("JSON 解析失败: " + idsJson, e);
        }
    }

    /**
     * 地址簿默认操作
     *
     * @param id
     * @param flag
     */
    @Override
    public void updateDefault(Long id, Integer flag) {

        //1. 参数校验
        if (id == null || flag == null){
            throw new ForbiddenOperationException("参数非法");
        }

        //2. 修改默认状态
        Long userId = UserContext.currentUserId();
        AddressBook addressBookDB = this.lambdaQuery().eq(AddressBook::getIsDefault, 1)
                .eq(AddressBook::getUserId,userId)
                .one();
        if (addressBookDB != null){
            boolean result = this.lambdaUpdate().set(AddressBook::getIsDefault, 0)
                    .eq(AddressBook::getId, addressBookDB.getId())
                    .update();
            if (!result){
                throw new DBException("更新默认地址失败");
            }
        }

        boolean result = this.lambdaUpdate().set(AddressBook::getIsDefault, flag)
                .eq(AddressBook::getId, id)
                .update();
        if (!result){
            throw new DBException("修改默认地址操作失败");
        }
    }

    /**
     * 获取默认地址
     *
     * @return
     */
    @Override
    public AddressBook getDefaultAddress() {
        Long userId = UserContext.currentUserId();
        AddressBook addressBook = this.lambdaQuery().eq(AddressBook::getUserId, userId)
                .eq(AddressBook::getIsDefault, 1)
                .one();
        if (addressBook == null){
            throw new ForbiddenOperationException("查询默认地址失败");
        }
        return addressBook;
    }
}
